﻿namespace ClassyBlog.DomainObjects.Specs.Unit
{
    using System;
    using System.Collections.Generic;

    using Machine.Specifications;

    [Subject(typeof(Blog))]
    public class when_posts_per_page_is_set
    {
        static int previous;

        Establish context = () => previous = Blog.DefaultPostPerPage;

        Because of = () => Blog.DefaultPostPerPage = 50;

        It should_be_same = () => Blog.DefaultPostPerPage.ShouldEqual(50);

        Cleanup on_exit = () => Blog.DefaultPostPerPage = previous;
    }

    [Subject(typeof(Blog))]
    public class when_pages_per_page_is_set
    {
        static int previous;

        Establish context = () => previous = Blog.DefaultPagesPerPage;

        Because of = () => Blog.DefaultPagesPerPage = 50;

        It should_be_same = () => Blog.DefaultPagesPerPage.ShouldEqual(50);

        Cleanup on_exit = () => Blog.DefaultPagesPerPage = previous;
    }

    [Subject(typeof(Blog))]
    public class when_default_theme_is_set
    {
        static string previous;

        Establish context = () => previous = Blog.DefaultTheme;

        Because of = () => Blog.DefaultTheme = "magic";

        It should_be_same = () => Blog.DefaultTheme.ShouldEqual("magic");

        Cleanup on_exit = () => Blog.DefaultTheme = previous;
    }

    [Subject(typeof(Blog))]
    public class when_blog_is_created
    {
        static Blog blog;

        Because of = () => blog = new Blog();

        It should_have_id = () => blog.Id.ShouldNotEqual(Guid.Empty);

        It should_have_default_posts_per_page = () =>
            blog.PostsPerPage.ShouldEqual(5);

        It should_have_default_pages_per_page = () =>
            blog.PagesPerPage.ShouldEqual(5);

        It should_have_default_theme = () =>
            blog.Theme.ShouldEqual("default");
    }

    [Subject(typeof(Blog))]
    public class when_blog_id_is_set
    {
        static Blog blog;
        static Guid id;

        Establish context = () =>
        {
            blog = new Blog();
            id = Guid.NewGuid();
        };

        Because of = () => blog.Id = id;

        It should_return_the_same = () => blog.Id.ShouldEqual(id);
    }

    [Subject(typeof(Blog))]
    public class when_setting_dynamic_property_of_blog
    {
        static Blog blog;
        static dynamic dynamicBlog;

        static string property;

        Establish context = () =>
        {
            blog = new Blog();

            dynamicBlog = blog;

            dynamicBlog.DummyProperty = "DynamicValue";
        };

        Because of = () => property = dynamicBlog.DummyProperty;

        It should_be_able_to_get = () => property.ShouldEqual("DynamicValue");
    }

    [Subject(typeof(Blog))]
    public class when_getting_regular_property_as_dynamic_property_of_blog
    {
        static Blog blog;
        static dynamic dynamicBlog;

        static string title;

        Establish context = () =>
        {
            blog = new Blog { Title = "Kazi Manzur Rashid" };
            dynamicBlog = blog;
        };

        Because of = () => title = dynamicBlog.Title;

        It should_be_able_to_get = () =>
            title.ShouldEqual("Kazi Manzur Rashid");
    }

    [Subject(typeof(Blog))]
    public class when_setting_regular_property_as_dynamic_property_of_blog
    {
        static Blog blog;
        static dynamic dynamicBlog;

        Establish context = () =>
        {
            blog = new Blog();
            dynamicBlog = blog;
        };

        Because of = () => dynamicBlog.Title = "Kazi Manzur Rashid";

        It should_be_able_to_set = () =>
            blog.Title.ShouldEqual("Kazi Manzur Rashid");
    }

    [Subject(typeof(Blog))]
    public class when_blog_dynamic_property_names_is_accessed
    {
        static Blog blog;
        static IEnumerable<string> dynamicPropertyNames;

        Establish context = () =>
        {
            blog = new Blog();
            blog.SetDynamicProperty("foo", "bar");
        };

        Because of = () => dynamicPropertyNames = blog.DynamicPropertyNames;

        It should_return_from_dynamic_property = () =>
            dynamicPropertyNames.ShouldContain("foo");
    }
}